<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Document</title>
  </head>
  <body>
    <!-- 
      组件的props选项
        作用：用于声明组件会接受到父组件传递过来的什么prop
        语法：
          1. props: ['propA', 'propB']
          2. props: {
            propA: String,        // 类型校验 - string
            propB: Number,        // 类型校验 - number
            propC: {
              type: String,       // 类型校验 - string
              required: true,     // 必须传递
              default: '张胜男'    // 默认值设置
            }
          }

     -->
    <div id="app">
      <!-- age 作为属性传递给组件 say-hi, 组件内，如果没有通过 props 声明会接受 age 的化，Vue不会将你传递过来的age代理到组件实例对象上。 -->
      <say-hi :name="aName" :age="18" year-money="1000"></say-hi>

      <hr />

      <say-hi name="李四" :age="20" sex="女" year-money="2000"></say-hi>

      <a-a-a-a></a-a-a-a>
    </div>

    <script src="../lib/vue.js"></script>
    <script>
      // 给 Vue.prototype 挂载一些属性和方法
      Vue.prototype.myName = "张三";
      Vue.prototype.say = function () {
        console.log(this.myName);
      };

      Vue.component("SayHi", {
        template: `
          <h2>Say Hello, {{ name }} - {{ age }} - {{ sex }}</h2>
        `,

        data() {
          return {
            a: 1,
            b: 2,
          };
        },

        // 声明我会接受到的prop数据有哪些
        // props: ["name"],

        props: {
          name: String, // 传递给我的name需要是一个字符串
          age: Number,
          sex: {
            type: String,
            default: "男", // 默认值设置
            // 自定义校验
            validator(value) {
              console.log("value", value);
              // 需要返回一个 boolean
              //  true - 表示校验通过
              //  false - 表示校验不通过
              return ["男", "女"].includes(value);
            },
          },
          yearMoney: {
            type: String,
            required: true, // 表示必须要传递该 prop
          },
          children: {
            type: Array,
            // 注意，如果默认值是一个引用数据类型的化，需要设置成函数返回的形式
            // default: [1, 2, 3],
            default() {
              return [1, 2, 3];
            },
          },
        },

        mounted() {
          // this - 当前组件的实例对象
          //    this.$data 组件data数据的一个对象
          //    this.$props 组件 接受到的 prop 数据的一个组合对象
          //    组件实例是通过 VueComponent 构造出来的，VueComponent 是继承了 Vue 的
          //        我们可以在 Vue.propotype 上挂载一些属性或方法，那么所有组件都可以通过 this 点出来
          console.log(this);
          console.log(this.myName);
          this.say();
        },
      });

      Vue.component("AAAA", {
        template: `
          <div>AAAA - {{myName}}</div>
        `,
      });

      const vm = new Vue({
        el: "#app",

        data() {
          return {
            aName: "张三",
          };
        },

        mounted() {
          console.log("Root this", this);
        },
      });
    </script>
  </body>
</html>
